

<template>
  <div class="pieChart" :id="id" />
</template>

<script>
import * as echarts from "echarts";
export default {
  props: {
    dataList: {
      type: Array,
      default: () => [
        {
          value: 100,
          name: "0-40岁",
        },
        {
          value: 23,
          name: "40-50岁",
        },
        {
          value: 23,
          name: "50-60岁",
        },
        {
          value: 23,
          name: "60-70岁",
        },
      ],
    },
    id: {
      type: String,
      default: "pieChart",
    },
    title: {
      type: String,
      default: "",
    },
    unit: {
      type: String,
      default: "例",
    },
    isVisibleTotal: {
      type: Boolean,
      default: true,
    },
    color: {
      type: Array,
      default: () => [
        "#4580E9",
        "#88C00B",
        "#5ED0FF",
        "#ACE0FE",
        "#F1900E",
        "#42A2B2",
        "#A449B2",
      ],
    },
  },
  data() {
    return {
      chart: null,
      screenWidth: null,
    };
  },
  mounted() {
    this.screenWidth = document.body.clientWidth;
    window.onresize = () => {
      return (() => {
        this.screenWidth = document.body.clientWidth;
      })();
    };
    this.$nextTick(() => {
      this.initChart();
    });
  },
  watch: {
    dataList: {
      handler() {
        this.$nextTick(() => {
          this.initChart();
        });
      },
      deep: true,
    },
    screenWidth: {
      handler(val) {
        this.initChart();
      },
    },
  },
  beforeDestroy() {
    if (!this.chart) {
      return;
    }
    this.chart.dispose();
    this.chart = null;
  },
  destroyed() {
    clearInterval(this.setInter);
  },
  methods: {
    initChart() {
      this.chart = echarts.init(this.$el);
      window.addEventListener("resize", this.chart.resize);
      this.chart.showLoading({
        text: "loading",
        color: "rgba(20, 149, 247, 0.7)",
        textColor: "#000",
        maskColor: "rgba(255, 255, 255, 0.2)",
        zlevel: 0,
      });
      const total = this.dataList
        .map((item) => item.qty)
        .reduce((acc, curr) => acc + curr, 0);
      const option = {
        color: this.color,
        legend: {
          orient: "vertical",
          left: "right",
          align: "left",
          itemWidth: 15,
          textStyle: {
            color: "#000",
          },
          formatter: (name) => {
            const data = this.dataList.find((item) => item.name == name);
            return `${name}: ${data.qty} ${this.unit} ${data.ratio}%`;
          },
        },
        title: [
          {
            text: this.title,
            bottom: "0",
            left: "center",
            textStyle: {
              fontSize: 16,
            },
          },
          {
            text: `总计： ${total} ${this.unit}`,
            right: this.screenWidth <= 750 ? 0 : "25%",
            show: this.isVisibleTotal,
            bottom: "0",
            align: "center",
            textStyle: {
              // color: "#108DE9",
              fontSize: 14,
              fontWeight: "normal",
            },
          },
        ],
        tooltip: {
          trigger: "item",
          formatter: (params) => {
            const data = params.data;
            return `${data.name}: ${data.qty} ${this.unit} ${data.ratio}%`;
          },
        },
        series: [
          {
            // name: this.title,
            // padAngle: 9,
            type: "pie",
            radius: "70%",
            label: {
              show: false,
              formatter: "{b}: {c}",
            },
            data: this.dataList,
          },
        ],
      };
      this.chart.setOption(option);
      setTimeout(() => {
        this.chart.hideLoading();
      }, 1000);
    },
  },
};
</script>

<style lang="less" scoped>
.pieChart {
  width: 100%;
  height: 100%;
}
</style>
